using System;
using System.Collections.Generic;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input.Touch;

namespace Pokemon
{
    internal class GameplayScreen : GameScreen
    {
        #region Attribute

        //Lop layer, quan ly toan man hinh
        private readonly LayerManager _layer;

        //private readonly List<GameComponent> _components;

        //Doi tuong thoi gian quan ly thoi gian cua man choi
        private TimeSpan timeSpan;

        //Doi thu may
        private AI _computer;

        //So luong zombie con lai
        private int _numZombie;

        //Cac unit bi huy
        private List<Unit> _destroyedUnits = new List<Unit>();

        #endregion

        public GameplayScreen(Game game) : base(game)
        {
            _layer = new LayerManager(game);
            game.Services.AddService(typeof(LayerManager), _layer);

            //Lop kiem tra input tu player, co do uu tien cao nhat
            InputManager inputManager = new InputManager(game, this);
            _layer.Add(inputManager, 9);
            game.Services.AddService(typeof(InputManager), inputManager);

            //Lop lo viec xu ly cac loai dan, co do uu tien sau input
            BulletManager bulletManager = new BulletManager(game);
            _layer.Add(bulletManager, 7);
            game.Services.AddService(typeof(BulletManager), bulletManager);

            //Lop lo viec xu ly soul
            SoulManager soulManager = new SoulManager(game);
            _layer.Add(soulManager, 6);
            game.Services.AddService(typeof(SoulManager), soulManager);

            //Lop lo viec xu ly boom
            BoomManager boomManager = new BoomManager(game);
            _layer.Add(boomManager, 6);
            game.Services.AddService(typeof(BoomManager), boomManager);

            //Event xu ly viec player tap len man hinh
            UserTapped += OnUserTappedInGameplayScreen;

            //Event xu ly su kien 1 pokemon duoc dat xuong
            PokemonDowned += PokemonDownInGrid;

            //Doi tuong AI, quan ly viec cho xuat cac zombie vao game
            _computer = new AI(this, @"Content/Maps/01.xml");

            //Doi tuong thoi gian, cho biet luong thoi gian da choi tu luc bat dau man choi.
            timeSpan = new TimeSpan(0);

            //Event xu ly su kien 1 zombie bi tieu diet
            ZombieDead += EndGame;
        }

        public int NumZombie
        {
            get { return _numZombie; }
            set { _numZombie = value; }
        }

        #region Draw & Update

        public override void Draw(GameTime gameTime)
        {
            ScreenManager.Game.GraphicsDevice.Clear(Color.White);
            
            ScreenManager.SpriteBatch.Begin();
            
            ScreenManager.SpriteBatch.Draw(_background, Vector2.Zero, Color.White);
            
            _layer.Draw(gameTime);

            //foreach (var gameComponent in _components)
            //{
            //    if (gameComponent is DrawableGameComponent)
            //        ((DrawableGameComponent) (gameComponent)).Draw(gameTime);
            //}

            ScreenManager.SpriteBatch.End();
        }

        public override void Update(GameTime gameTime)
        {
            timeSpan += gameTime.ElapsedGameTime;

            if (_destroyedUnits.Count > 0)
                foreach (var destroyedUnit in _destroyedUnits)
                {
                    destroyedUnit.Dispose();
                }

            _destroyedUnits.Clear();

            _computer.Update(timeSpan);

            _layer.Update(gameTime);

            //foreach (var gameComponent in _components)
            //{
            //    gameComponent.Update(gameTime);
            //}

            //BulletManager.Update(gameTime);
        }

        #endregion

        #region Load & Unload Content

        public override void LoadContent()
        {
            //add PanelButton
            _background = ScreenManager.Game.Content.Load<Texture2D>(@"Textures\Backgrounds\actionBackground");
            PanelButton panelButton = new PanelButton(CurrGame, this, @"Content/Panels/GameplayPanels/PanelDef.xml");
            _layer.Add(panelButton, 3);

            //add Grid
            Grid grid = new Grid(CurrGame, this, @"Content/Grids/GameplayScreens/MainGridDef.xml");
            grid.ShowGridLine();
            _layer.Add(grid, 0);
          
            //add Chest
            Chest chest = new Chest(CurrGame, this, @"Content/Textures/Chest/ChestDef.xml", new Vector2(120, 400));            
            _layer.Add(chest, 5);

            //add Shop
            Shop shop = new Shop(CurrGame, this, @"Content/Textures/Shop/ShopDef.xml", new Vector2(120,10));            
            shop.Chest = chest;
            _layer.Add(shop, 5);

            //Lop quan ly dan
            Bullet.AddGame(_currGame);
            Bullet.AddSpriteBatch(_screenManager.SpriteBatch);

            //Dan set
            Lightning.AddPath(@"Content/Skills/Lightning/LightningDef.xml");
            Lightning.Initialize();

            //Dan gio
            Gust.AddPath(@"Content/Skills/Gust/GustDef.xml");
            Gust.Initialize();

            //Dan bang
            Freeze.AddPath(@"Content/Skills/Freeze/FreezeDef.xml");
            Freeze.Initialize();

            //Dan lua
            Fire.AddPath(@"Content/Skills/Fire/FireDef.xml");
            Fire.Initialize();

            //Dan beam
            Beam.AddPath(@"Content/Skills/Beam/BeamDef.xml");
            Beam.Initialize();

            base.LoadContent();
        }

        public override void UnloadContent()
        {
            _background.Dispose();
            base.UnloadContent();
        }

        #endregion

        #region Event: Raise when user tap on the screen

        public delegate void TappedDelegate(object sender, Point p);

        public event TappedDelegate UserTapped;

        public void OnUserTapped(Point p)
        {
            TappedDelegate handler = UserTapped;
            if (handler != null) handler(this, p);
        }

        public void OnUserTappedInGameplayScreen(object sender, Point p)
        {
            GameComponent gc = CheckComponentClick(p);
        }

        private GameComponent CheckComponentClick(Point p)
        {
            if (!_layer.CheckComponentClick(p))
            {
                _layer.FailClick();
            }
            return null;
        }

        #endregion

        #region Support Method
        /// <summary>
        /// Lay ra blank chua the pokemon da dc user chon - neu co
        /// </summary>
        /// <returns>Blank dc nhan</returns>
        public PushalbeBlank GetPanelGridPushBlank()
        {
            List<PanelButton> p = GetPanelButton();
            if (p != null)
                foreach (var panelButton in p)
                {
                    if (panelButton.GetPushBlank() != null)
                        return panelButton.GetPushBlank();
                }
            return null;            
        }

        #endregion

        #region Event: Raise when user tap on panelButton

        public delegate void PokemonBought();

        public event PokemonBought PokemonDowned;

        public void OnPokemonDowned()
        {
            PokemonBought handler = PokemonDowned;
            if (handler != null) handler();
        }

        /// <summary>
        /// Lay ra doi tuong PanelButton cua gameplayScreen
        /// </summary>
        /// <returns></returns>
        private List<PanelButton> GetPanelButton()
        {
            return _layer.GetPanelButton();
        }

        /// <summary>
        /// Pokemon duoc dat vao vi tri
        /// </summary>
        public void PokemonDownInGrid()
        {
            List<PanelButton> p = GetPanelButton();
            if (p != null)
                foreach (var panelButton in p)
                {
                    panelButton.GridPushed();
                }                
        }

        #endregion

        #region Event: Xay ra khi zombie bi tieu diet

        public delegate void ZombieEvent();

        public event ZombieEvent ZombieDead;

        public void OnZombieDead()
        {
            ZombieEvent handler = ZombieDead;
            if (handler != null) handler();
        }

        /// <summary>
        /// Ham kiem tra ket thuc game
        /// </summary>
        public void EndGame()
        {
            _numZombie--;
            if (_numZombie <= 0)
                CurrGame.Exit();
        }

        #endregion

        /// <summary>
        /// Khi 1 unit bi destroy thi se duoc dua vao _destroyUnits -> ko duoc update va draw nua
        /// </summary>
        /// <param name="unit"></param>
        public void UnitDestroy(Unit unit)
        {
            _destroyedUnits.Add(unit);
        }
    }
}
